package io.renren.wechat.controller;

import io.renren.wechat.common.aes.WXBizCmdCrypt;
import io.renren.wechat.common.aes.WXBizCorpCrypt;
import io.renren.wechat.common.aes.WXBizMsgCrypt;
import io.renren.wechat.service.suite.SuiteTicketService;
import io.renren.wechat.support.WXPayUtil;
import org.apache.commons.io.IOUtils;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpStatus;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;

import javax.servlet.ServletInputStream;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.nio.charset.StandardCharsets;
import java.util.Map;


/**
 * 系统回调URL
 */
@Controller
@RequestMapping({"/wechat/suite", "/wechat/system"})
public class WechatSystemEventController {
    private static final Logger LOGGER = LoggerFactory.getLogger(WechatSystemEventController.class);
    private WXBizCorpCrypt corpCrypt;


    @RequestMapping("/corp")
    public void corpCallback(@RequestParam("msg_signature") String msgSignature,
                             @RequestParam("timestamp") String timestamp,
                             @RequestParam("nonce") String nonce,
                             @RequestParam("echostr") String echoStr,
                             HttpServletResponse response) {
        LOGGER.info("get corpCallback parameters: msgSignature=[{}], timestamp=[{}], nonce=[{}], echostr=[{}]",
                msgSignature, timestamp, nonce, echoStr);
        try {
            final String plainMsgText = corpCrypt.VerifyURL(msgSignature, timestamp, nonce, echoStr);
            LOGGER.info("recvMsgNotify plainMsgText: [{}]", plainMsgText);

            response.getWriter().print(plainMsgText);
        } catch (Exception e) {
            LOGGER.error("recvMsgNotify failed", e);
            response.setStatus(HttpStatus.BAD_REQUEST.value());
        }
    }

    @PostMapping("/corp")
    public void data(@RequestParam("msg_signature") String msgSignature,
                     @RequestParam("timestamp") String timestamp,
                     @RequestParam("nonce") String nonce,
                     HttpServletRequest request,
                     HttpServletResponse response) throws Exception {
        try (final ServletInputStream inputStream = request.getInputStream()) {
            LOGGER.debug("post recvDataNotify parameters: msgSignature=[{}], timestamp=[{}], nonce=[{}]",
                    msgSignature, timestamp, nonce);

            final String requestBody = IOUtils.toString(inputStream, StandardCharsets.UTF_8);
            LOGGER.debug("request body: {}", requestBody);
            if (StringUtils.isBlank(requestBody)) {
                LOGGER.warn("request_body_is_empty!!!");
                response.getWriter().print("success");
                return;
            }

            final String xmlMsg = corpCrypt.DecryptMsg(msgSignature, timestamp, nonce, requestBody);
            LOGGER.debug("request xml msg: {}", xmlMsg);

            final Map<String, String> dataMap = WXPayUtil.xmlToMap(xmlMsg);
            final String infoType = dataMap.get("InfoType");
            LOGGER.debug("recv data infoType: {}", infoType);

            response.getWriter().print("success");
        }
    }

    @Autowired
    public void setCorpCrypt(WXBizCorpCrypt corpCrypt) {
        this.corpCrypt = corpCrypt;
    }
}
